/* Copyright 2013 Guillaume Nodet.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
* implied.
*
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.ops4j.pax.web.service.jetty.internal;
import static org.junit.Assert.assertEquals;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.net.URL;
import java.security.cert.X509Certificate;
import java.util.*;
import javax.servlet.Servlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.eclipse.jetty.servlet.DefaultServlet;
import org.eclipse.jetty.util.component.Container;
import org.junit.Test;
import org.ops4j.pax.web.service.WebContainerContext;
import org.ops4j.pax.web.service.spi.model.ContextModel;
import org.ops4j.pax.web.service.spi.model.ServerModel;
import org.ops4j.pax.web.service.spi.model.ServletModel;
import org.osgi.framework.Bundle;
import org.osgi.framework.BundleContext;
import org.osgi.framework.BundleException;
import org.osgi.framework.BundleListener;
import org.osgi.framework.Constants;
import org.osgi.framework.Filter;
import org.osgi.framework.FrameworkListener;
import org.osgi.framework.InvalidSyntaxException;
import org.osgi.framework.ServiceFactory;
import org.osgi.framework.ServiceListener;
import org.osgi.framework.ServiceObjects;
import org.osgi.framework.ServiceReference;
import org.osgi.framework.ServiceRegistration;
import org.osgi.framework.Version;
import org.osgi.service.http.HttpContext;
public class HandlerDestructionTest {
//CHECKSTYLE:OFF
@Test
public void testHandler() throws Exception {
ServerModel serverModel = new ServerModel();
JettyServerImpl server = new JettyServerImpl(serverModel, null);
server.start();
TestListener listener = new TestListener();
JettyServerWrapper container = server.getServer();
container.addBean(listener);
WebContainerContext httpContext = new WebContainerContext() {
@Override
public Set<String> getResourcePaths(String name) {
return Collections.emptySet();
}
@Override
public String getContextId() {
return "test";
}
public boolean handleSecurity(HttpServletRequest request,
HttpServletResponse response) throws IOException {
return false;
}
public URL getResource(String name) {
return null;
}
public String getMimeType(String name) {
return null;
}
};
Bundle testBundle = new Bundle() {
@Override
public int compareTo(Bundle arg0) {
return 0;
}
@Override
public int getState() {
return 0;
}
@Override
public void start(int options) throws BundleException {
}
@Override
public void start() throws BundleException {
}
@Override
public void stop(int options) throws BundleException {
}
@Override
public void stop() throws BundleException {
}
@Override
public void update(InputStream input) throws BundleException {
}
@Override
public void update() throws BundleException {
}
@Override
public void uninstall() throws BundleException {
}
@Override
public Dictionary<String, String> getHeaders() {
Dictionary<String, String> dict = new Hashtable<>();
dict.put(Constants.BUNDLE_VERSION, "1.0.0");
return dict;
}
@Override
public long getBundleId() {
return 0;
}
@Override
public String getLocation() {
return null;
}
@Override
public ServiceReference<?>[] getRegisteredServices() {
return null;
}
@Override
public ServiceReference<?>[] getServicesInUse() {
return null;
}
@Override
public boolean hasPermission(Object permission) {
return false;
}
@Override
public URL getResource(String name) {
return null;
}
@Override
public Dictionary<String, String> getHeaders(String locale) {
return null;
}
@Override
public String getSymbolicName() {
return "HandlerDestructorTest-SymbolicNameBundle";
}
@Override
public Class<?> loadClass(String name)
throws ClassNotFoundException {
return null;
}
@Override
public Enumeration<URL> getResources(String name)
throws IOException {
return null;
}
@Override
public Enumeration<String> getEntryPaths(String path) {
return null;
}
@Override
public URL getEntry(String path) {
return null;
}
@Override
public long getLastModified() {
return 0;
}
@Override
public Enumeration<URL> findEntries(String path,
String filePattern, boolean recurse) {
return null;
}
@Override
public BundleContext getBundleContext() {
return new BundleContext() {
@Override
public boolean ungetService(
ServiceReference<?> reference) {
return false;
}
@Override
public void removeServiceListener(
ServiceListener listener) {
}
@Override
public void removeFrameworkListener(
FrameworkListener listener) {
}
@Override
public void removeBundleListener(BundleListener listener) {
}
@Override
public <S> ServiceRegistration<S> registerService(
Class<S> clazz, S service,
Dictionary<String, ?> properties) {
return null;
}
@Override
public ServiceRegistration<?> registerService(
String clazz, Object service,
Dictionary<String, ?> properties) {
return null;
}
@Override
public ServiceRegistration<?> registerService(
String[] clazzes, Object service,
Dictionary<String, ?> properties) {
return null;
}
@Override
public Bundle installBundle(String location,
InputStream input) throws BundleException {
return null;
}
@Override
public Bundle installBundle(String location)
throws BundleException {
return null;
}
@Override
public <S> Collection<ServiceReference<S>> getServiceReferences(
Class<S> clazz, String filter)
throws InvalidSyntaxException {
return null;
}
@Override
public ServiceReference<?>[] getServiceReferences(
String clazz, String filter)
throws InvalidSyntaxException {
return null;
}
@Override
public <S> ServiceReference<S> getServiceReference(
Class<S> clazz) {
return null;
}
@Override
public ServiceReference<?> getServiceReference(
String clazz) {
return null;
}
@Override
public <S> S getService(ServiceReference<S> reference) {
return null;
}
@Override
public String getProperty(String key) {
return null;
}
@Override
public File getDataFile(String filename) {
return null;
}
@Override
public Bundle[] getBundles() {
return null;
}
@Override
public Bundle getBundle(String location) {
return null;
}
@Override
public Bundle getBundle(long id) {
return null;
}
@Override
public Bundle getBundle() {
return null;
}
@Override
public ServiceReference<?>[] getAllServiceReferences(
String clazz, String filter)
throws InvalidSyntaxException {
return null;
}
@Override
public Filter createFilter(String filter)
throws InvalidSyntaxException {
return null;
}
@Override
public void addServiceListener(
ServiceListener listener, String filter)
throws InvalidSyntaxException {
}
@Override
public void addServiceListener(ServiceListener listener) {
}
@Override
public void addFrameworkListener(
FrameworkListener listener) {
}
@Override
public void addBundleListener(BundleListener listener) {
}
@Override
public <S> ServiceRegistration<S> registerService(Class<S> clazz, ServiceFactory<S> factory,
Dictionary<String, ?> properties) {
return null;
}
@Override
public <S> ServiceObjects<S> getServiceObjects(ServiceReference<S> reference) {
return null;
}
};
}
@Override
public Map<X509Certificate, List<X509Certificate>> getSignerCertificates(
int signersType) {
return null;
}
@Override
public Version getVersion() {
return null;
}
@Override
public <A> A adapt(Class<A> type) {
return null;
}
@Override
public File getDataFile(String filename) {
return null;
}
};
{
Servlet servlet = new DefaultServlet();
ContextModel contextModel = new ContextModel(httpContext,
testBundle, getClass().getClassLoader());
ServletModel servletModel = new ServletModel(contextModel, servlet,
"/", null, null, null);
server.addServlet(servletModel);
server.removeServlet(servletModel);
}
final Set<Object> oldbeans = new HashSet<>(container.getBeans());
Servlet servlet = new DefaultServlet();
ContextModel contextModel = new ContextModel(httpContext,
testBundle, getClass().getClassLoader());
ServletModel servletModel = new ServletModel(contextModel, servlet,
"/", null, null, null);
server.addServlet(servletModel);
// assertNotSame("OldSize:"+oldbeans.size()+" new size: "+container.getBeans().size(),
// oldbeans.size(), container.getBeans().size());
server.removeServlet(servletModel);
// System.out.println(listener.diff(oldbeans));
assertEquals(oldbeans.size(), container.getBeans().size());
}
//CHECKSTYLE:OFF
/*
* private static String format(Container.Relationship relationship) {
* return relationship.getParent() + "---" + relationship.getRelationship()
* + "-->" + relationship.getChild(); }
*/
static class TestListener implements Container.Listener {
final WeakHashMap<Object, String> beans = new WeakHashMap<>();
@Override
public void beanAdded(Container parent, Object bean) {
System.out.println("Adding bean " + bean);
beans.put(bean, bean.toString());
}
@Override
public void beanRemoved(Container parent, Object bean) {
System.out.println("Removing bean " + bean);
beans.remove(bean);
}
/*
* final WeakHashMap<Object, String> beans = new WeakHashMap<Object,
* String>(); final WeakHashMap<String,
* List<org.eclipse.jetty.util.component.Container.Relationship>>
* relations = new WeakHashMap<String,
* List<org.eclipse.jetty.util.component.Container.Relationship>>();
*
* public void addBean(Object bean) { System.out.println("Adding bean "
* + bean); beans.put(bean, bean.toString()); }
*
* public void removeBean(Object bean) {
* System.out.println("Removing bean " + bean); String b =
* beans.remove(bean); if (b != null) { List<Container.Relationship>
* beanRelations = relations.remove(b); if (beanRelations != null) {
* List<Container.Relationship> removeList = new
* ArrayList<Container.Relationship>( beanRelations); for
* (Container.Relationship relation : removeList) {
* relation.getContainer().update(relation.getParent(),
* relation.getChild(), null, relation.getRelationship(), true); } } } }
*
* public void add(
* org.eclipse.jetty.util.component.Container.Relationship relationship)
* { System.out.println("Adding relationship " + format(relationship));
* String parent = beans.get(relationship.getParent()); if (parent ==
* null) { addBean(relationship.getParent()); parent =
* beans.get(relationship.getParent()); } String child =
* beans.get(relationship.getChild()); if (child == null) {
* addBean(relationship.getChild()); child =
* beans.get(relationship.getChild()); } if (parent != null && child !=
* null) { List<org.eclipse.jetty.util.component.Container.Relationship>
* rels = relations .get(parent); if (rels == null) { rels = new
* ArrayList<org.eclipse.jetty.util.component.Container.Relationship>();
* relations.put(parent, rels); } rels.add(relationship); } }
*
* public void remove(
* org.eclipse.jetty.util.component.Container.Relationship relationship)
* { System.out.println("Removing relationship " +
* format(relationship)); String parent =
* beans.get(relationship.getParent()); String child =
* beans.get(relationship.getChild()); if (parent != null && child !=
* null) { List<org.eclipse.jetty.util.component.Container.Relationship>
* rels = relations .get(parent); if (rels != null) { for
* (Iterator<org.eclipse.jetty.util.component.Container.Relationship> i
* = rels .iterator(); i.hasNext();) {
* org.eclipse.jetty.util.component.Container.Relationship r = i
* .next(); if (relationship.equals(r) || r.getChild() == null) {
* i.remove(); } } } } }
*
* public WeakHashMap<Object, String> getBeans() { return beans; }
*
* public WeakHashMap<String,
* List<org.eclipse.jetty.util.component.Container.Relationship>>
* getRelations() { return relations; }
*
* public String toString() { StringBuilder sb = new StringBuilder();
* for (Object bean : beans.keySet()) {
* sb.append("Bean ").append(bean).append("\n"); } for (String key :
* relations.keySet()) { for
* (org.eclipse.jetty.util.component.Container.Relationship r :
* relations .get(key)) {
* sb.append("Relation ").append(format(r)).append("\n"); } } return
* sb.toString(); }
*
* public String diff(Set<Object> oldbeans) { StringBuilder sb = new
* StringBuilder(); for (Object bean : beans.keySet()) { if
* (!oldbeans.contains(bean)) {
* sb.append("Bean ").append(bean).append("\n"); } } for (String key :
* relations.keySet()) { for
* (org.eclipse.jetty.util.component.Container.Relationship r :
* relations .get(key)) { if
* (!oldbeans.contains(r.getChild().toString()) ||
* !oldbeans.contains(r.getParent().toString())) {
* sb.append("Relation ").append(format(r)).append("\n"); } } } return
* sb.toString(); }
*/
}
}